home *** CD-ROM | disk | FTP | other *** search
/ Windows Expert / Windows Expert.iso / program / wintech1.zip / LEVARO.ZIP / TOOLBAR.C < prev    next >
Text File  |  1991-09-27  |  10KB  |  357 lines

  1. /*
  2.  * TOOLBAR.C -- Tool Bar control
  3.  */
  4.  
  5. #include <windows.h>
  6. #include "toolbar.h"
  7.  
  8. #define MAXTOOLBARBM    255           /* Maximum bitmaps.           */
  9. #define TBNOSELECT    MAXTOOLBARBM + 1   /* No selection made.       */
  10.  
  11. static char szBorderProp[]  = "BORDER";    /* Border width property.   */
  12. static char szSizeProp[]    = "SIZE";      /* Tool bar size property.  */
  13. static char szUnitProp[]    = "UNIT";      /* Atomic size property.    */
  14. static char szToolBitProp[] = "TOOLBITS";  /* Array of RECTs handle.   */
  15. static char szNumBitmaps[]  = "NUMBMS";    /* # of bitmaps received.   */
  16.  
  17. static int HitTest( int x, int y, LPRECT lpRects, int nNumBitmaps )
  18. {
  19.  
  20.     /* Examine the array of bitmap RECTs to see if x,y is contained    */
  21.     /* in one.                                   */
  22.  
  23.     int     nBitmap;
  24.     POINT   point;
  25.  
  26.     point.x = x;
  27.     point.y = y;
  28.  
  29.     /* Iterate through the array of RECTS and see if the point (x,y)   */
  30.     /* is contained in any of them.                       */
  31.  
  32.     for (nBitmap = 0; nBitmap < nNumBitmaps; nBitmap++)
  33.     {
  34.     if (PtInRect( lpRects+nBitmap, point ) )
  35.         return nBitmap;
  36.     }
  37.  
  38.     return TBNOSELECT;
  39.  
  40. }
  41.  
  42.  
  43. static void SetToolBarState( HWND hwnd, int iState )
  44. {
  45.  
  46.     /* Change the state of the toolbar and invalide the client area    */
  47.     /* so that a WM_PAINT message is generated.                */
  48.  
  49.     if ( GET_TBSTATE != iState )
  50.     InvalidateRect( hwnd, NULL, FALSE );
  51.     SET_TBSTATE( iState );
  52.  
  53. }
  54.  
  55. static void PaintToolBar( HWND hwnd, HDC hdc )
  56. {
  57.  
  58.     /* Display the tool bar on the screen by sending a series of       */
  59.     /* TB_TOOLBAR messages to the parent window and constructing       */
  60.     /* the tool bar accordingly.  The tool bar is finished and ready   */
  61.     /* to be displayed when the parent stops responding.           */
  62.  
  63.     int     nPos, x, y;
  64.     int     nHoriz;
  65.     int     nVert;
  66.     HDC     hdcMem, hdcBitmap;
  67.     HBITMAP    hBitmap;
  68.     HBITMAP    hToolBarBitmap;
  69.     RECT    clientRect;
  70.     int     nBorder;
  71.     int     nXUnit, nYUnit;
  72.     HANDLE    hToolBarBM;
  73.     int     nNumBitmaps;
  74.     int     nMaxPos;
  75.     LPRECT    lpRects;
  76.     BITMAP    bm;
  77.     RECT    bmRect;
  78.  
  79.     /* Get parameters passed when the tool bar was created.  These     */
  80.     /* were saved in the property lists.                   */
  81.  
  82.     nBorder = GetProp( hwnd, szBorderProp );
  83.     nXUnit  = GetProp( hwnd, szUnitProp ) >> 8;
  84.     nYUnit  = GetProp( hwnd, szUnitProp ) & 0x00FF;
  85.     nHoriz  = GetProp( hwnd, szSizeProp ) >> 8;
  86.     nVert   = GetProp( hwnd, szSizeProp ) & 0x00FF;
  87.  
  88.     /* Get array of RECTs (cells).  The handle is a a property, and    */
  89.     /* get the pointer to the list.                       */
  90.  
  91.     hToolBarBM = GetProp( hwnd, szToolBitProp );
  92.     lpRects = (LPRECT) GlobalLock( hToolBarBM );
  93.  
  94.     GetClientRect( hwnd, &clientRect );
  95.  
  96.     /* Set up a bitmap for drawing the tool bar                */
  97.  
  98.     hdcMem = CreateCompatibleDC( hdc );
  99.  
  100.     hToolBarBitmap = CreateCompatibleBitmap( hdc,
  101.                          clientRect.right,
  102.                          clientRect.bottom );
  103.  
  104.     SelectObject( hdcMem, hToolBarBitmap );
  105.     SetMapMode( hdcMem, GetMapMode( hdc ) );
  106.  
  107.     /* Fill in background colors, first the gray border.           */
  108.  
  109.     FillRect( hdcMem, &clientRect, GetStockObject( LTGRAY_BRUSH ) );
  110.  
  111.     /* Then the black inner area.                       */
  112.  
  113.     InflateRect( &clientRect, -nBorder, -nBorder );
  114.     FillRect( hdcMem, &clientRect, GetStockObject( BLACK_BRUSH ) );
  115.     InflateRect( &clientRect, nBorder, nBorder );
  116.  
  117.     hdcBitmap = CreateCompatibleDC( hdc );
  118.  
  119.     nMaxPos    = nHoriz * nVert;   /* Compute max grid positions.     */
  120.     nNumBitmaps = 0;
  121.  
  122.     /* Iterate through all possible cell positions.               */
  123.  
  124.     for ( nPos = 0; nPos < nMaxPos; nPos++ )
  125.     {
  126.     SET_TBBITMAP( hwnd, 0 );
  127.  
  128.     /* Get a bitmap from the parent by sending a message.  The    */
  129.     /* high-order word of the LONG parameter is the bitmap number */
  130.     /* and the low-order word is the 1 if it is selected, and 0   */
  131.     /* otherwise.                              */
  132.  
  133.     SendMessage( GetParent(hwnd),TB_TOOLBAR,hwnd,
  134.              MAKELONG( nNumBitmaps,
  135.                  ((nNumBitmaps == GET_TBSTATE) ? TRUE : FALSE)));
  136.  
  137.     hBitmap = GET_TBBITMAP;
  138.     if (hBitmap)
  139.     {
  140.  
  141.         /* Use HitTest to see if the cell position is occupied.    */
  142.  
  143.         do
  144.         {
  145.         x = ((nPos * nXUnit) % (nHoriz * nXUnit)) +
  146.             nBorder + ((nPos % nHoriz) + 1);
  147.         y = ((nPos / nHoriz) * nYUnit) + nBorder +
  148.             ((nPos / nHoriz) + 1);
  149.         } while ( (HitTest( x, y, lpRects, nNumBitmaps ) != TBNOSELECT)
  150.                               && (nPos++ < nMaxPos) );
  151.  
  152.         if (nPos == nMaxPos)
  153.         break;
  154.  
  155.         /* Set up bitmap dimensions for the array of RECTs, and    */
  156.         /* add it to the list of RECTs (cells).               */
  157.  
  158.         GetObject( hBitmap, sizeof(BITMAP), (LPSTR) &bm );
  159.         bmRect.left   = x;
  160.         bmRect.top      = y;
  161.         bmRect.right  = x + bm.bmWidth  + 1;
  162.         bmRect.bottom = y + bm.bmHeight + 1;
  163.  
  164.         lpRects[ nNumBitmaps++ ] = bmRect;
  165.  
  166.         SelectObject( hdcBitmap, hBitmap );
  167.         SetMapMode( hdcBitmap, GetMapMode( hdc ) );
  168.  
  169.         /* Copy position bitmap to tool bar bitmap.            */
  170.  
  171.         BitBlt( hdcMem, x, y, bm.bmWidth, bm.bmHeight,
  172.                           hdcBitmap, 0, 0, SRCCOPY );
  173.  
  174.     }
  175.     if ( nNumBitmaps > MAXTOOLBARBM )
  176.         break;
  177.     }
  178.  
  179.     DeleteDC( hdcBitmap );
  180.  
  181.     /* Copy the tool bar bitmap to screen.                   */
  182.  
  183.     BitBlt( hdc, 0, 0, clientRect.right, clientRect.bottom,
  184.                         hdcMem, 0, 0, SRCCOPY );
  185.  
  186.     DeleteDC( hdcMem );
  187.     DeleteObject( hToolBarBitmap );
  188.  
  189.     SetProp( hwnd, szNumBitmaps, nNumBitmaps );
  190.     GlobalUnlock( hToolBarBM );
  191.  
  192. }
  193.  
  194. LONG FAR PASCAL ToolBarWndFn(HWND hwnd,   WORD message,
  195.                  WORD wParam, LONG lParam)
  196. {
  197.  
  198.     /* This is the main window procedure of the tool bar.  Its main    */
  199.     /* job is to display the tool bar on the screen and detect mouse   */
  200.     /* mouse clicks within it.    If the tool bar state changes, the     */
  201.     /* the parent is notified and the tool bar is updated.           */
  202.  
  203.     int     x, y;
  204.     PAINTSTRUCT ps;
  205.     HDC     hdc;
  206.     HANDLE    hToolBarBM;
  207.     int     nNumBitmaps;
  208.     LPRECT    lpRects;
  209.     int     nResult;
  210.  
  211.     switch (message)
  212.     {
  213.     case WM_CREATE:
  214.  
  215.         SET_TBSTATE( TBNOSELECT );      /* Initially, no selection   */
  216.  
  217.         /* Activate ourselves so we appear active.               */
  218.  
  219.         SendMessage( hwnd, WM_NCACTIVATE, 1, 0L );
  220.  
  221.         break;
  222.  
  223.     case WM_LBUTTONDOWN:
  224.     case WM_LBUTTONDBLCLK:
  225.  
  226.         BringWindowToTop( hwnd );
  227.  
  228.         /* Get the array of RECTs and the size of the array.       */
  229.  
  230.         hToolBarBM    = GetProp( hwnd, szToolBitProp );
  231.         lpRects    = (LPRECT) GlobalLock( hToolBarBM );
  232.         nNumBitmaps = GetProp( hwnd, szNumBitmaps );
  233.  
  234.         x = LOWORD(lParam);
  235.         y = HIWORD(lParam);
  236.  
  237.         nResult = HitTest( x, y, lpRects, nNumBitmaps );
  238.  
  239.         /* If a selection is made, change state and send a message */
  240.         /* to our parent.                           */
  241.  
  242.         if (nResult != TBNOSELECT)
  243.         {
  244.         SetToolBarState( hwnd, nResult );
  245.         SendMessage( GetParent(hwnd), TB_CLICKED, hwnd,
  246.                         MAKELONG( nResult, 0 ) );
  247.         }
  248.  
  249.         GlobalUnlock( hToolBarBM );
  250.         break;
  251.  
  252.     case WM_ERASEBKGND:
  253.  
  254.         /* Swallow the message; the background need not be painted */
  255.  
  256.         return TRUE;
  257.  
  258.     case WM_PAINT:
  259.  
  260.         hdc = BeginPaint( hwnd, &ps );
  261.  
  262.         PaintToolBar( hwnd, hdc );
  263.  
  264.         EndPaint( hwnd , &ps );
  265.  
  266.         return TRUE;
  267.  
  268.     case TB_SETSELECT:
  269.  
  270.         if (wParam)
  271.         SetToolBarState( hwnd, LOWORD(lParam) );
  272.         else
  273.         SetToolBarState( hwnd, TBNOSELECT );
  274.  
  275.         return TRUE;
  276.  
  277.     case TB_GETSELECT:
  278.  
  279.         return GET_TBSTATE;
  280.  
  281.     case WM_NCACTIVATE:
  282.  
  283.         wParam = TRUE;               /* Enforce activation.  */
  284.  
  285.         break;
  286.  
  287.     case WM_DESTROY:
  288.  
  289.         RemoveProp( hwnd, szBorderProp );
  290.         RemoveProp( hwnd, szUnitProp );
  291.         RemoveProp( hwnd, szSizeProp );
  292.  
  293.         hToolBarBM = GetProp( hwnd, szToolBitProp );
  294.         GlobalFree( hToolBarBM );
  295.  
  296.         RemoveProp( hwnd, szToolBitProp );
  297.         RemoveProp( hwnd, szNumBitmaps );
  298.  
  299.         break;
  300.  
  301.     default:
  302.  
  303.         break;
  304.  
  305.     }
  306.  
  307.      return DefWindowProc (hwnd, message, wParam, lParam);
  308. }
  309.  
  310.  
  311. HWND FAR PASCAL CreateToolBar( HANDLE hInstance, HWND hWndApp,
  312.                    DWORD dwStyle, int x, int y,
  313.                    int nXUnit, int nYUnit,
  314.                    int nHoriz, int nVert,
  315.                    int nBorder, LPSTR lpTitle )
  316. {
  317.  
  318.     /* This function creates a new tool bar.  It saves most of its     */
  319.     /* information in the form of window properties so that the window */
  320.     /* procedure can retrieve them when necessary.               */
  321.  
  322.     int     nHeight, nWidth;
  323.     HWND    hToolBarWnd;
  324.     HANDLE  hToolBarBM;
  325.  
  326.     nWidth  = (nHoriz * nXUnit) + (nBorder * 2) + (nHoriz+1) +
  327.                (2 * GetSystemMetrics( SM_CXBORDER ) );
  328.     nHeight = (nVert  * nYUnit) + (nBorder * 2) + (nVert+1) +
  329.                 GetSystemMetrics( SM_CYCAPTION ) +
  330.                 GetSystemMetrics( SM_CYBORDER  );
  331.  
  332.     hToolBarWnd = CreateWindow( "ToolBar", lpTitle,
  333.                 dwStyle | WS_CHILD | WS_CLIPSIBLINGS,
  334.                 x, y,
  335.                 nWidth,
  336.                 nHeight,
  337.                 hWndApp, NULL,
  338.                 hInstance, NULL );
  339.  
  340.     SetProp( hToolBarWnd, szBorderProp, nBorder );
  341.     SetProp( hToolBarWnd,   szUnitProp, (nXUnit << 8) + nYUnit );
  342.     SetProp( hToolBarWnd,   szSizeProp, (nHoriz << 8) + nVert  );
  343.  
  344.     /* Allocate memory for the maximum number of bitmaps. This is    */
  345.     /* the list of cells that is used to determine the position of   */
  346.     /* the bitmaps within the client area of the tool bar.         */
  347.  
  348.     hToolBarBM = GlobalAlloc( GMEM_SHARE | GMEM_ZEROINIT,
  349.                     sizeof(RECT) * MAXTOOLBARBM );
  350.     if ( hToolBarBM )
  351.      SetProp( hToolBarWnd, szToolBitProp, hToolBarBM );
  352.     SetProp( hToolBarWnd, szNumBitmaps, 0 );
  353.  
  354.     return hToolBarWnd;
  355.  
  356. }
  357.